//////////////////////////////////////////////////////////////////////////
// $Id: RenderTexture.cpp,v 1.1 2009/04/03 12:46:11 sunjun Exp $
//////////////////////////////////////////////////////////////////////////

#include "Local.h"

//////////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////////

NAMESPACE_BEGIN

//////////////////////////////////////////////////////////////////////////

	RenderTexture::RenderTexture( const Context* rc ) : Texture(rc) 
	{
		for ( U32 i = 0; i < 6; i++ ) mSHandle[i] = NULL;
	}

	RenderTexture::~RenderTexture() 
	{
		for ( U32 i = 0; i < 6; i++ )
		{
			if((IDirect3DSurface9*)mSHandle[i]){((IDirect3DSurface9*)mSHandle[i])->Release(); mSHandle[i] = NULL;}
		}
	}

	//////////////////////////////////////////////////////////////////////////
	
	/*
	====================
	load
	====================
	*/
	INLINE VOID RenderTexture::load( const VOID* data, U32 size )
	{
		CHECK(data);

		// check the data header
		U8 * data_ptr = (U8*)data;

		// get the type
		U32 type = *(U32*)data_ptr;
		data_ptr += sizeof(U32);

		// get the format
		U32 format = *(U32*)data_ptr;
		data_ptr += sizeof(U32);

		// get the width
		U32 width = *(U32*)data_ptr;
		data_ptr += sizeof(U32);		

		HRESULT hr;
		if( type == TT_TEXTURE )
		{
			// get the height
			U32 height = *(U32*)data_ptr;
			data_ptr += sizeof(U32);

			// create the render texture
			IDirect3DTexture9 *d3d9Texture = NULL;
			hr = ((IDirect3DDevice9*)mRCPtr->handle())->CreateTexture(width, height, 0, D3DUSAGE_RENDERTARGET, (D3DFORMAT)format, D3DPOOL_DEFAULT, &d3d9Texture, NULL);
			if(FAILED(hr)) MAssert(VA("RenderTexture::load : create the render texture is failed(%s)!", DXGetErrorDescription(hr)));
			
			// get the surface of the render texture
			IDirect3DSurface9 *d3d9Surface = NULL;
			hr = d3d9Texture->GetSurfaceLevel(0, &d3d9Surface);
			if(FAILED(hr)) MAssert(VA("RenderTexture::load : get the surface level of the texture(%s)!", DXGetErrorDescription(hr)));
			mSHandle[0] = (HANDLE)d3d9Surface;

			// get the base texture
			hr = d3d9Texture->QueryInterface(IID_IDirect3DBaseTexture9, (VOID **)&mHandle);
			if(FAILED(hr)) MAssert(VA("RenderTexture::load : can't get base texture(%s)!", DXGetErrorDescription(hr)));
			if( d3d9Texture ){ d3d9Texture->Release(), d3d9Texture = NULL; }
		}
		else if( type == TT_CUBEMAP )
		{
			// create the cube render texture
			IDirect3DCubeTexture9 *d3d9CubeTexture = NULL;
			hr = ((IDirect3DDevice9*)mRCPtr->handle())->CreateCubeTexture(width, 0, D3DUSAGE_RENDERTARGET, (D3DFORMAT)format, D3DPOOL_DEFAULT, &d3d9CubeTexture, NULL);
			if(FAILED(hr)) MAssert(VA("RenderTexture::load : create the render cube texture is failed(%s)!", DXGetErrorDescription(hr)));

			// get the surface of the render texture
			for ( U32 i = 0; i < 6; i++ )
			{
				IDirect3DSurface9 *d3d9Surface = NULL;
				hr = d3d9CubeTexture->GetCubeMapSurface((D3DCUBEMAP_FACES)i, 0, &d3d9Surface);
				if(FAILED(hr)) MAssert(VA("RenderTexture::load : get the surface level of the cube texture(%s)!", DXGetErrorDescription(hr)));
				mSHandle[i] = (HANDLE)d3d9Surface;
			}		

			// get the base texture
			hr = d3d9CubeTexture->QueryInterface(IID_IDirect3DBaseTexture9, (VOID **)&mHandle);
			if(FAILED(hr)) MAssert(VA("RenderTexture::load : can't get base texture(%s)!", DXGetErrorDescription(hr)));
			if( d3d9CubeTexture ){ d3d9CubeTexture->Release(), d3d9CubeTexture = NULL; }
		}
		else
		{
			MAssert(VA("RenderTexture::load : the type is unsupported(%d)!", type));
		}
	}

//////////////////////////////////////////////////////////////////////////

NAMESPACE_END

//////////////////////////////////////////////////////////////////////////
